﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Diagnostics;
using System.IO;
using Microsoft.Xna.Framework.Input;
using PloobsEngine.Input;
using PloobsEngine.Commands;

namespace PloobsEngine.DataAquisition
{
    public enum CompressType
    {
        RAW,AVERAGE
    }

    public class FileSaverDataHandler : DataHandlers
    {

        public FileSaverDataHandler(String fileName, Keys saveKey)
        {
            this.fileName = fileName;
            this.saveKey = saveKey;
            this.ct = CompressType.RAW;

            InputPlayableKeyBoard ip1 = new SimpleConcreteKeyboardInputPlayable(StateKey.PRESS, saveKey, saveFile, EntityType.TOOLS);
            BindKeyCommand mm = new BindKeyCommand(ip1, BindAction.ADD);
            CommandProcessor.getCommandProcessor().SendCommandSyncronous(mm, InputAdvanced.MyName);          
        }

        public FileSaverDataHandler(String fileName, Keys saveKey, int averageTicks)
        {
            this.fileName = fileName;
            this.saveKey = saveKey;
            this.ct = CompressType.AVERAGE;
            this.avtime = averageTicks;

            InputPlayableKeyBoard ip1 = new SimpleConcreteKeyboardInputPlayable(StateKey.PRESS, saveKey, saveFile, EntityType.TOOLS);
            BindKeyCommand mm = new BindKeyCommand(ip1, BindAction.ADD);
            CommandProcessor.getCommandProcessor().SendCommandSyncronous(mm, InputAdvanced.MyName);
        }

        private void raw()
        {
            foreach (var itemx in values.Keys)
            {
                StreamWriter sw = new StreamWriter(fileName + "_" + itemx + ".csv" , true);
                int i = 0;
                sw.WriteLine("frame , " + itemx );
                foreach (var item in values[itemx])
                {
                   sw.WriteLine(i + "," + item);
                    i++;
                }                
                sw.Close();          
            }
            
        }
        private void min_average()
        {           
            foreach (var itemx in values.Keys)
            {
                int i = 0;
                int j = 0;
                double media = 0;
                StreamWriter sw = new StreamWriter(fileName + "_" + itemx + ".csv", true);
                sw.WriteLine("frame , " + itemx);
                foreach (var item in values[itemx])
                {
                    if (i == avtime)
                    {
                        sw.WriteLine(j + "," + item);
                        media= 0;
                        i=0;
                    }
                    media += item;   
                    i++;
                    j++;
                }                
                sw.Close();    
            }
           
        }

        private void saveFile(InputPlayableKeyBoard ipk)
        {          
            switch (ct)
            {
                case CompressType.RAW:
                    raw();
                    break;
                case CompressType.AVERAGE:
                    min_average();
                    break;
                default:
                    break;
            }
            
            values.Clear();
            hand.Clear();
            fpstype.Clear();
        }
        
        #region DataHandlers Members
        private String fileName = null;
        CompressType ct;
        Keys? saveKey = null;
        int avtime;
        private Dictionary<String, Stopwatch> hand = new Dictionary<string, Stopwatch>();
        private Dictionary<String,List<double>> values = new Dictionary<String,List<double>>();
        private List<FpsType> fpstype = new List<FpsType>();
                
        public void HandleData(DataFormat data)
        {
            if (data is MethodDataFormat)
            {
                MethodDataFormat dat = data as MethodDataFormat;
                if (dat.Part == MethodPart.START)
                {
                    if (!hand.ContainsKey(dat.MethodName))
                    {
                        Stopwatch sw = new Stopwatch();
                        sw.Start();
                        hand[dat.MethodName] = sw;
                        values[dat.MethodName] = new List<double>();
                    }
                    else
                    {
                        hand[dat.MethodName].Start();
                    }
                }
                else 
                {
                    if (hand.ContainsKey(dat.MethodName))
                    {
                        Stopwatch old = hand[dat.MethodName];
                        old.Stop();
                        values[dat.MethodName].Add(old.Elapsed.TotalMilliseconds);
                        old.Reset();
                    }
                }
            }
            else if (data is FpsDataFormat)
            {
                FpsDataFormat dat = data as FpsDataFormat;
                if (fpstype.Contains(dat.FpsType))
                {
                    values[dat.FpsTypeString].Add(dat.Fps);
                }
                else
                {
                    values[dat.FpsTypeString] = new List<double>();
                    values[dat.FpsTypeString].Add(dat.Fps);
                    fpstype.Add(dat.FpsType);
                }
            }

            else if (data is SingleNumberDataFormat)
            {
                SingleNumberDataFormat dat = data as SingleNumberDataFormat;
                
                if (values.ContainsKey(dat.Origin))
                {
                    values[dat.Origin].Add(dat.Number);
                }
                else
                {
                    values[dat.Origin] = new List<double>();
                    values[dat.Origin].Add(dat.Number);                    
                }
            }    


        }

        public Type[] GetHandledType
        {
            get { return new Type[] { typeof(MethodDataFormat), typeof(SingleNumberDataFormat), typeof(FpsDataFormat) }; }
        }

        #endregion
    }
}
